package com.chagee.channel.server.controller.lark;

import com.alibaba.fastjson.JSONObject;
import com.chagee.base.utils.HttpResponse;
import com.chagee.base.utils.HttpResponseUtil;
import com.chagee.channel.api.bo.lark.ApprovalInstanceDetailBO;
import com.chagee.channel.api.bo.lark.FileUploadResultBO;
import com.chagee.channel.api.bo.lark.StartApprovalBO;
import com.chagee.channel.api.bo.lark.UploadFileBO;
import com.chagee.channel.api.bo.lark.UploadFileByUrlVO;
import com.chagee.channel.api.bo.lark.UploadFileUrlBO;
import com.chagee.channel.api.bo.lark.UploadFileVO;
import com.chagee.channel.common.constant.LarkConstant;
import com.chagee.channel.common.exception.BizErrorCode;
import com.chagee.channel.server.event.service.LarkService;
import com.chagee.channel.server.util.ValidationResult;
import com.chagee.channel.server.util.ValidationUtils;
import io.swagger.annotations.ApiOperation;
import java.util.Collections;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.validation.Valid;
import lombok.RequiredArgsConstructor;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.apache.rocketmq.shaded.commons.lang3.math.NumberUtils;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

/**
 * 飞书http接口
 *
 * @author: chang.jiawei
 * @date: 2024/01/18
 */
@RestController
@RequiredArgsConstructor
@Slf4j
@RequestMapping("/lark")
public class LarkController {

    private final LarkService larkService;

    @SneakyThrows
    @PostMapping("/upload/file")
    @ApiOperation("上传文件至飞书,用于审批")
    HttpResponse<FileUploadResultBO> uploadFile(@Valid UploadFileVO uploadFile) {
        if (uploadFile.getFile().getBytes().length == NumberUtils.INTEGER_ZERO) {
            return HttpResponseUtil.build(null, BizErrorCode.FILE_TOO_SMALL.getErrorCode(), BizErrorCode.FILE_TOO_SMALL.getErrorMsg());
        }
        return HttpResponseUtil.success(larkService.upload2Lark(UploadFileBO.transfer(uploadFile)));
    }

    @SneakyThrows
    @PostMapping("/feign/upload/file")
    @ApiOperation("上传文件至飞书,用于审批(Feign调用)")
    HttpResponse<FileUploadResultBO> uploadFile(@RequestBody @Valid UploadFileBO uploadFile) {
        if (uploadFile.getFile().length == NumberUtils.INTEGER_ZERO) {
            return HttpResponseUtil.build(null, BizErrorCode.FILE_TOO_SMALL.getErrorCode(), BizErrorCode.FILE_TOO_SMALL.getErrorMsg());
        }
        return HttpResponseUtil.success(larkService.upload2Lark(uploadFile));
    }

    @PostMapping("/callback")
    @ApiOperation("飞书回调事件专用,暂时支持只审批实例状态消息")
    public JSONObject callback(@RequestBody JSONObject body, HttpServletRequest request) {
        log.info("lark callback body: {}", body);
        if (body.containsKey(LarkConstant.EVENT_CHALLENGE_KEY)) {
            //第一次绑定该接口，返回绑定参数
            Map<String, String> result = Collections.singletonMap(LarkConstant.EVENT_CHALLENGE_KEY, body.getString(LarkConstant.EVENT_CHALLENGE_KEY));
            return (JSONObject) JSONObject.toJSON(result);
        }
        if (!larkService.checkSignature(body, request)) {
            return new JSONObject();
        }
        JSONObject param = larkService.decrypt(body.getString("encrypt"));
        return larkService.handleCallback(param);
    }

    @PostMapping("/manual/callback")
    @ApiOperation("手动模拟飞书回调事件")
    public JSONObject manualCallback(@RequestBody JSONObject param) {
        return larkService.handleCallback(param);
    }

    @PostMapping("/subscribe/all/approval")
    @ApiOperation("订阅所有配置文件中的审批")
    public HttpResponse<Void> subscribeAllApproval() {
        larkService.subscribeAllApproval();
        return HttpResponseUtil.success(null);
    }

    @PostMapping("/subscribe/approval")
    @ApiOperation("订阅审批")
    public HttpResponse<Void> subscribeApproval(@RequestBody String code) {
        larkService.subscribeApproval(code);
        return HttpResponseUtil.success(null);
    }

    @PostMapping("/unsubscribe/approval")
    @ApiOperation("取消订阅审批")
    public HttpResponse<Void> unsubscribeApproval(@RequestBody String code) {
        larkService.unsubscribeApproval(code);
        return HttpResponseUtil.success(null);
    }


    @PostMapping("/approval/approvalInstanceDetail")
    @ApiOperation("获取审批详情")
    public ApprovalInstanceDetailBO approvalInstanceDetail(@RequestBody String code) {
        ApprovalInstanceDetailBO approvalInstanceDetailBO = larkService.approvalInstanceDetail(code);
        return approvalInstanceDetailBO;
    }


    @PostMapping("/approval/start")
    @ApiOperation("发起审批")
    public HttpResponse<String> approvalStart(@Valid @RequestBody StartApprovalBO startApprovalBO) {
        ValidationResult validationResult = ValidationUtils.validateEntity(startApprovalBO);
        if (validationResult.isHasErrors()) {
            return HttpResponseUtil.failure(validationResult.toString());
        }
        return HttpResponseUtil.success(larkService.startApprove(startApprovalBO));
    }

    @SneakyThrows
    @PostMapping("/upload/fileByUrl")
    @ApiOperation("根据文件url上传文件至飞书,用于审批")
    HttpResponse<FileUploadResultBO> uploadFileByUrl(@Valid @RequestBody UploadFileByUrlVO uploadFile) {
        return HttpResponseUtil.success(larkService.uploadFileByUrl(UploadFileUrlBO.transfer(uploadFile)));
    }

}
